//-------------------------------------------------------------------
//	Copyright (c) 2010-2012  Zhirnov Andrey
//	This file is part of the "UXGEN" project.
//	See copyright notice in "Engine.h".
//-------------------------------------------------------------------

#ifndef _UX_SOUND_EFFECTS_H
#define _UX_SOUND_EFFECTS_H

#include <Includes.h>

namespace Engine
{
namespace Resources
{

	//
	// Sound Filter
	//

	class _EXPORT_ CSoundFilter : private CReferenced, public CEngBaseObject
	{
	protected:
		ALuint			_uIdent;
		al_filter::type	_eType;

	private:
		virtual void _Release()		{ delete this; }

	public:
		CSoundFilter();
		virtual ~CSoundFilter();

		bool Create(al_filter::type eType);
		void Destroy();


		ALuint			GetIdent()		const	{ return _uIdent; }
		al_filter::type	GetFilterType()	const	{ return _eType; }

		// CEngBaseObject //
		virtual void Release()		{ delete this; }
	};



	//
	// Sound Effect
	//

	class _EXPORT_ CSoundEffect : private CReferenced, public CEngBaseObject
	{
	protected:
		ALuint			_uIdent;
		al_effect::type	_eType;

	private:
		virtual void _Release()		{ delete this; }

	public:
		CSoundEffect();
		virtual ~CSoundEffect();

		bool Create(al_effect::type eType);
		void Destroy();
		
		ALuint			GetIdent()		const	{ return _uIdent; }
		al_effect::type	GetEffectType()	const	{ return _eType; }

		// CEngBaseObject //
		virtual void Release()		{ delete this; }
	};



	//
	// Sound Effect AUX Slot
	//

	class _EXPORT_ CSoundEffectSlot : private CReferenced, public CEngBaseObject
	{
	protected:
		CSoundEffectPtr		_pEffect;
		ALuint				_uIdent;

	private:
		virtual void _Release()		{ delete this; }

	public:
		CSoundEffectSlot();
		virtual ~CSoundEffectSlot();

		bool Create();
		void Destroy();

		void SetEffect(const CSoundEffectPtr &pEf);
		void SetVolume(float fValue);
		
		ALuint					GetIdent()	const	{ return _uIdent; }
		const CSoundEffectPtr &	GetEffect()	const	{ return _pEffect; }

		// CEngBaseObject //
		virtual void Release()		{ delete this; }
	};

	


//--------------------------- CSoundFilter ------------------------//

	inline CSoundFilter::CSoundFilter(): _uIdent(0), _eType(al_filter::UNKNOWN)
	{}

	inline CSoundFilter::~CSoundFilter()
	{
		Destroy();
	}

	inline bool CSoundFilter::Create(al_filter::type eType)
	{
		Destroy();

		AL_CALL_R( alGenFilters( 1, &_uIdent ) );
		AL_CALL_R( alFilteri( _uIdent, AL_FILTER_TYPE, eType ) );
		_eType = eType;

		return true;
	}

	inline void CSoundFilter::Destroy()
	{
		if ( _uIdent != 0 )
		{
			AL_CALL( alDeleteFilters( 1, &_uIdent ) );
			_uIdent = 0;
		}
		_eType	= al_filter::UNKNOWN;
	}


//-------------------------- CSoundEffect -------------------------//

	inline CSoundEffect::CSoundEffect(): _uIdent(0), _eType(al_effect::UNKNOWN)
	{}

	inline CSoundEffect::~CSoundEffect()
	{
		Destroy();
	}

	inline bool CSoundEffect::Create(al_effect::type eType)
	{
		Destroy();

		AL_CALL_R( alGenEffects( 1, &_uIdent ) );
		AL_CALL_R( alEffecti( _uIdent, AL_EFFECT_TYPE, eType ) );
		_eType = eType;

		return true;
	}

	inline void CSoundEffect::Destroy()
	{
		if ( _uIdent != 0 )
		{
			AL_CALL( alDeleteEffects( 1, &_uIdent ) );
			_uIdent = 0;
		}
		_eType = al_effect::UNKNOWN;
	}



//---------------------- CSoundEffectSlot -------------------------//

	inline CSoundEffectSlot::CSoundEffectSlot(): _uIdent(0)
	{}

	inline CSoundEffectSlot::~CSoundEffectSlot()
	{
		Destroy();
	}

	inline bool CSoundEffectSlot::Create()
	{
		Destroy();

		AL_CALL_R( alGenAuxiliaryEffectSlots( 1, &_uIdent ) );
		return true;
	}

	inline void CSoundEffectSlot::Destroy()
	{
		if ( _uIdent != 0 )
		{
			AL_CALL( alDeleteAuxiliaryEffectSlots( 1, &_uIdent ) );
			_uIdent = 0;
		}
	}

	inline void CSoundEffectSlot::SetEffect(const CSoundEffectPtr &pEf)
	{
		_pEffect = pEf;
		AL_CALL( alAuxiliaryEffectSloti( _uIdent, AL_EFFECTSLOT_EFFECT,
							_pEffect != nullptr ? _pEffect->GetIdent() : 0 ) );
	}

	inline void CSoundEffectSlot::SetVolume(float fValue)
	{
		AL_CALL( alAuxiliaryEffectSlotf( _uIdent, AL_EFFECTSLOT_GAIN, fValue ) );
	}

//-------------------------------------------------------------------

}	// Resources
}	// Engine

#endif	// _UX_SOUND_EFFECTS_H